package com.sharp.core;

import org.lwjgl.input.Keyboard;
import org.lwjgl.input.Mouse;
import org.lwjgl.opengl.Display;


/**
 *
 * @author sharp
 */
public abstract class Scene {
	
	private boolean run;
	private int tick;							// összes tick
	private int fps;
	private int performance;
	private int tickPerSec;
	private int deltaTick;

	/**
	 * @return 
	 * @throws Exception
	 * @TODO
	 */
	abstract public boolean init() throws Exception ;

	/**
	 * @TODO
	 */
	abstract public void deInit();

	/**
	 * @TODO
	 */
	protected abstract void logic();
	protected abstract void render();
	protected abstract boolean isActive();
	protected abstract boolean isCloseRequested();
	protected abstract void click(int x, int y, int btn);
	protected abstract void mouseWheel(int d);
	
	public Scene(int tickPerSec) {
		run = true;
		setTickPerSec(tickPerSec);
	}

	final public void stop() {
		run = false;
	}

	final public int getTick() {
		return tick;
	}


	final public int getFps() {
		return fps;
	}

	final public int getPerfomance() {
		return performance;
	}

	final public void setTickPerSec(int tickPerSec) {
		this.tickPerSec = tickPerSec;
		deltaTick = 1000/tickPerSec;
	}

	final public int getTickPerSec() {
		return tickPerSec;
	}


	/**
	 *
	 */
	final public void run() {
		int mouseWheel;
		try {
			if (init() == false) {
				return;
			}
			Mouse.create();
			Keyboard.create();
		} catch (Exception ex) {
			ex.printStackTrace();
			return;
		}

		long end, sleep;
		while( run && (isCloseRequested() == false) ) {
			if ( true || Display.isActive() ) {
				end = System.currentTimeMillis() + deltaTick;

				if ( Mouse.isButtonDown(0) )
					click(Mouse.getX(), Mouse.getY(), 0);
				if ( (mouseWheel=Mouse.getDWheel()) != 0 )
					mouseWheel(mouseWheel);
				logic();
				render();
				try {
					sleep = end - System.currentTimeMillis();
					performance = (int)(((float)deltaTick/(deltaTick-sleep+1))*100);
					Thread.sleep( Math.max(0, sleep) );
				} catch (InterruptedException ex) {}
				++tick;
			} else {
				try {
					Thread.sleep(200);
				} catch (InterruptedException ex) {}
			}
		}

		deInit();
	}
}